package com.study.zookeeper.service;

import org.apache.curator.framework.CuratorFramework;
import org.apache.curator.framework.recipes.cache.*;
import org.apache.zookeeper.data.Stat;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

@Service
public class CacheService {

    @Autowired
    private CuratorFramework curatorClient;

    /**
     * 监听路径下面的所有节点
     */
    public void pathCache() {
        //注意去掉sleep后，部分监听会丢失，不可以频繁修改
        try {
            PathChildrenCache pathChildrenCache = new PathChildrenCache(curatorClient, "/home/wufaliang", true);
            pathChildrenCache.start();
            PathChildrenCacheListener cacheListener = (curatorClient, event) -> {
                System.out.println("事件类型:" + event.getType());
                if (event.getData() != null) {
                    System.out.println("节点数据：" + event.getData().getPath() + "=" + new String(event.getData().getData()));
                }
            };

            pathChildrenCache.getListenable().addListener(cacheListener);
            curatorClient.create().creatingParentContainersIfNeeded().forPath("/home/wufaliang/abc", "haha".getBytes());
            //Thread.sleep(10);
            curatorClient.create().creatingParentContainersIfNeeded().forPath("/home/wufaliang/dbc", "xixi".getBytes());
            //Thread.sleep(10);
            curatorClient.setData().forPath("/home/wufaliang/abc", "zhongguoren".getBytes());
            //Thread.sleep(10);
            for (ChildData data : pathChildrenCache.getCurrentData()) {
                System.out.println("getCurrentData：" + data.getPath() + "=" + new String(data.getData()));
            }
            curatorClient.delete().forPath("/home/wufaliang/dbc");
            //Thread.sleep(10);
            pathChildrenCache.close();
        } catch (Exception e) {

        }
    }

    /**
     * 监听特定节点
     */
    public void nodeCache() {
        try {
            NodeCache nodeCache = new NodeCache(curatorClient, "/home/flwu2");
            nodeCache.getListenable().addListener(new NodeCacheListener() {
                @Override
                public void nodeChanged() throws Exception {
                    if (nodeCache.getCurrentData() != null) {
                        System.out.println("节点内容变化：" + new String(nodeCache.getCurrentData().getData()));
                        System.out.println("hello world");
                    } else {
                        System.out.println("节点已经被删除了");
                    }
                }
            });
            nodeCache.start();
            curatorClient.setData().forPath("/home/flwu2", "wufaliang".getBytes());
            Thread.sleep(100);
            curatorClient.delete().forPath("/home/flwu2");
            Thread.sleep(100);
            nodeCache.close();
        } catch (Exception e) {
            System.out.println(e.getMessage());
        }

    }

    /**
     * 可以监控整个树上的所有节点，类似于pathCache 和nodecache的组合
     * 这个方法不需要sleep
     */
    public void treeCache() {
        try {
            String path = "/home/flwu/zookeeper";
            Stat stat =  curatorClient.checkExists().forPath(path);
            if (stat == null) {
                String result = curatorClient.create().creatingParentContainersIfNeeded().forPath(path, "myhome".getBytes());
                System.out.println("创建action : " + result);
            }
            TreeCache treeCache = new TreeCache(curatorClient, path);
            treeCache.getListenable().addListener((curatorClient, event) -> {
                if (event.getType().equals(TreeCacheEvent.Type.NODE_REMOVED))  {
                    System.out.println("已删除");
                }else if(event.getType().equals(TreeCacheEvent.Type.INITIALIZED)) {
                    System.out.println("初始化");
                } else {
                    System.out.println("even-type: " + event.getType());
                    System.out.println("even-data: " + event.getData().getData());
                }
            });
            treeCache.start();
            //触发监听
            curatorClient.setData().forPath(path, "nishishui".getBytes());
            curatorClient.setData().forPath(path, "zhongguancun".getBytes());
            curatorClient.delete().forPath(path);
            treeCache.close();
        } catch (Exception e) {
            System.out.println(e.getMessage());
        }

    }
}
